/*
 * CS_MARKET_ITEM_SALE_LIST_V2.cpp
 *
 *  Created on: 2013. 12. 23.
 *      Author: mega
 */

#include "../../Command.h"
#include "../../User.h"
#include "../../NState/Static.h"
#include "../../NLogic/NAsync/AsyncTrade.h"

namespace ProjectZ { namespace NCommand {

void SendFailMarketItemSaleList(User * pUser, int res)
{
	::Network::Packet * pAck = ::Network::GETPACKETPOOL()->SEND_NEW();
	*pAck << static_cast<int16_t>(res);
	*pAck << static_cast<uint16_t>(0);
	*pAck << static_cast<uint8_t>(0);
	pAck->MakePacket(CMD_SC_MARKET_ITEM_SALE_LIST_V2);
	pUser->Send(pAck);
}

void Command::CS_MARKET_ITEM_SALE_LIST_V2(User * pUser, ::Network::Packet * pPacket)
{
	/*
	// 거래소 아이템 리스트 요청_V2
	CS_MARKET_ITEM_SALE_LIST_V2		0x100E
	{
		s8 class_type;			/// -1 전체
		s8 item_type;			/// 아이템 시트 타입
		s16 item_level_min;		/// 기본값은 본인레벨 client
		s16 item_level_max;		/// -1 없음
		s8 item_qulity;			/// -1 전체 등급
		u16 offset;				// 요청 데이터 시작점(0부터~)		[2013/12/13 이정우] u16 으로 변경해야함
		u8 interval;			// 요청할 개수
	}

	// 거래소 내 목록
	SC_MARKET_ITEM_SALE_LIST_V2	0x100F
	{
		s16 ack;	 			/// 성공(1),  실패(-1), 등록된 데이터 없음(-2)
		u16 searched_item_count;	/// 99페이지 상한선 (MAX : 2970)으로 최종 협의됨
		u8	count
		{
			u64	item_seq;					// 아이템 seq
			u8	class_type;					// 장착클래스 타입
			u8	sub_type;					// 서브타입
			u16	tid;						// 테이블 아이디
			u8	cur_refine_step;			// 현재 제련단계
			u8	level;						// 아이템 레벨
			u8	quality;
			u8	open_upgrade_stone_slot; 	// 오픈된 강화석 슬롯수
			u8	evolve_step;		 		// 진화단계
			u8	evolve_max; 		 		// 진화 최대단계
			u8	eff_type0;				 	// 0 : + , 1 : %
			u16	eff_value0;				 	// 기본이펙트 : 효과치
			u32	sale_price;		 			// 판매가격
			s24	sale_id;		 			// 판매자 아이디
			u8	sale_due_time;		 		// 남은시간(1시간 미만인 경우 0)
			u8	set_type					// 세트아이템타입(-1 : 없음)	추가됨
		}
	}*/

	PREPARE_PACKET;

	int8_t classType	= 0;
	int8_t sheetType	= 0;
	int16_t minLevel	= 0;
	int16_t maxLevel	= 0;
	int8_t itemQuality	= 0;
	uint16_t startIndex	= 0;
	uint8_t endIndex	= 0;

	*pPacket >> classType >> sheetType >> minLevel >> maxLevel >> itemQuality >> startIndex >> endIndex;

	if (4 != (maxLevel - minLevel))
	{
		DEBUGLOG("%s : INVALID LEVEL RANGE. min=%d, max=%d", __FUNCTION__, minLevel, maxLevel);
		SendFailMarketItemSaleList(pUser, ACK_UNKNOWN_ERROR);
		return;
	}

	NLogic::NAsync::AsyncTrade * pAsyncTrade = pUser->GetAsyncTrade();
	if (NULL == pAsyncTrade)
	{
		DEBUGLOG("%s : pAsyncTrade is NULL", __FUNCTION__);
		SendFailMarketItemSaleList(pUser, ACK_UNKNOWN_ERROR);
		return;
	}

	pAsyncTrade->GetData().class_type	= classType;
	pAsyncTrade->GetData().sheet_type	= sheetType;
	pAsyncTrade->GetData().min_level	= minLevel;
	pAsyncTrade->GetData().max_level	= maxLevel;
	pAsyncTrade->GetData().quality		= itemQuality;
	pAsyncTrade->GetData().start_index	= startIndex;
	pAsyncTrade->GetData().end_index	= endIndex;

	pUser->SetState(NState::Static::Instance().WAITTRADEITEMLOOKUP());

	Database::Command * pCommand = Database::GETCOMMANDPOOL()->NEW();

	pCommand->SetQueryType(::Database::Command::S_PROCEDURE);
	pCommand->MakeQuery("call sp_select_trade_item_count(%d,%d,%d,%d,%d,%d)",
			pAsyncTrade->GetData().class_type, pAsyncTrade->GetData().sheet_type,
			pAsyncTrade->GetData().min_level, pAsyncTrade->GetData().max_level,
			pAsyncTrade->GetData().quality, pUser->GetUserSeq());
	pCommand->SetObserver(pUser);
	pCommand->SetCommandId(DB_TRADEITEM_LOOKUP_COUNT);

	if (false == Database::GETSESSION()->AsyncExecute(static_cast<int>(DatabaseType::TRADE_SLAVE), pCommand))
	{
		DEBUGLOG("%s : AsyncExecute Fail", __FUNCTION__);

		SendFailMarketItemSaleList(pUser, ACK_DB_ERROR);
		pUser->SetState(NState::Static::Instance().MAINFRIENDLIST());

		Database::GETCOMMANDPOOL()->DEL(pCommand);

		return;
	}










#if 0
	int8_t classType	= 0;
	int8_t sheetType	= 0;
	int16_t minLevel	= 0;
	int16_t maxLevel	= 0;
	int8_t itemQuality	= 0;
	uint16_t startIndex	= 0;
	uint8_t endIndex	= 0;

	*pPacket >> classType >> sheetType >> minLevel >> maxLevel >> itemQuality >> startIndex >> endIndex;

	if (4 != (maxLevel - minLevel))
	{
		DEBUGLOG("%s : INVALID LEVEL RANGE. min=%d, max=%d", __FUNCTION__, minLevel, maxLevel);
		SendFailMarketItemSaleList(pUser, ACK_UNKNOWN_ERROR);
		return;
	}


	int registTotalCount = 0;

	{
		// 조건에 맞는 전체 아이템의 갯수 계산 (클라이언트에서 페이징 처리를 위해)
		::Database::Command::Auto clsAuto(::Database::GETCOMMANDPOOL());
		clsAuto->SetQueryType(::Database::Command::S_PROCEDURE);
		clsAuto->MakeQuery("call sp_select_trade_item_count(%d,%d,%d,%d,%d,%d)",
				classType, sheetType, minLevel, maxLevel, itemQuality, pUser->GetUserInfo().userseq);

		DEBUGLOG("CS_MARKET_ITEM_SALE_LIST_V2 : %s", clsAuto->GetQueryString());

		if (false == ::Database::GETSESSION()->SyncExecute(static_cast<int>(DatabaseType::TRADE_SLAVE), clsAuto))
		{
			DEBUGLOG("CS_MARKET_ITEM_SALE_LIST_V2 : false == ::Database::GETSESSION()->SyncExecute(1, clsAuto) Count!!");
			SendFailMarketItemSaleList(pUser, ACK_DB_ERROR);
			return;
		}

		if (clsAuto->GetErrorIdx() != 0)
		{
			DEBUGLOG("CS_MARKET_ITEM_SALE_LIST_V2 : clsAuto->GetErrorIdx() != 0 Count!!");
			SendFailMarketItemSaleList(pUser, ACK_DB_ERROR);
			return;
		}

		while (clsAuto->Next())
		{
			clsAuto->GetRecord() >> registTotalCount;
		}
	}


	{
		// 거래소에 등록된 아이템 정보 조회
		::Database::Command::Auto clsAuto(::Database::GETCOMMANDPOOL());
		clsAuto->SetQueryType(::Database::Command::S_PROCEDURE);
		clsAuto->MakeQuery("call sp_select_trade_item_v2(%d,%d,%d,%d,%d,%d,%d,%d)",
				classType, sheetType, minLevel, maxLevel, itemQuality, startIndex, endIndex, pUser->GetUserInfo().userseq);

		DEBUGLOG("CS_MARKET_ITEM_SALE_LIST_V2 : %s", clsAuto->GetQueryString());

		if (false == ::Database::GETSESSION()->SyncExecute(static_cast<int>(DatabaseType::TRADE_SLAVE), clsAuto))
		{
			DEBUGLOG("CS_MARKET_ITEM_SALE_LIST_V2 : false == ::Database::GETSESSION()->SyncExecute(1, clsAuto)");
			SendFailMarketItemSaleList(pUser, ACK_DB_ERROR);
			return;
		}

		if (clsAuto->GetErrorIdx() != 0)
		{
			DEBUGLOG("CS_MARKET_ITEM_SALE_LIST_V2 : clsAuto->GetErrorIdx() != 0");
			SendFailMarketItemSaleList(pUser, ACK_DB_ERROR);
			return;
		}

		::Network::Packet * pAck = ::Network::GETPACKETPOOL()->SEND_NEW();
		*pAck << static_cast<int16_t>(ACK_OK);
		*pAck << static_cast<uint16_t>(registTotalCount);
		*pAck << static_cast<uint8_t>(clsAuto->ResultRowCount());

		while (clsAuto->Next())
		{
			uint64_t tradeSeq		= 0;
			uint16_t tid			= 0;
			char curRefineStep		= 0;
			char level				= 0;
			char quality			= 0;
			char openUpstoneSlot	= 0;
			char evolveStep			= 0;
			char evolveMax			= 0;
			char effType_0			= 0;
			uint16_t effValue_0		= 0;
			int itemPrice			= 0;
			char remainHour			= 0;
			char setType			= 0;
			Toolkit::Str<81> nickname;

			clsAuto->GetRecord() >> tradeSeq >> itemPrice >> tid >> curRefineStep
					>> quality >> openUpstoneSlot >> evolveStep >> evolveMax
					>> effType_0 >> effValue_0 >> nickname >> level >> remainHour >> setType;

			*pAck << tradeSeq << classType << sheetType << tid << curRefineStep
					<< level << quality << openUpstoneSlot << evolveStep << evolveMax
					<< effType_0 << effValue_0 << itemPrice << nickname.c_str() << remainHour << setType;
		}

		pAck->MakePacket(CMD_SC_MARKET_ITEM_SALE_LIST_V2);
		pUser->Send(pAck);
	}
#endif
}

} /*NCommand*/ } /*ProjectZ*/

